<template>
  <div class="image-style-panel">
    <div class="text-style-panel">
      <div class="info">基本信息</div>
      <div class="row">
        <InputNumber
          prefix="X: "
          :step="5"
        :max="times"
        :maxlength="3"
          :value="left"
          @change="value => updateLeft(value as number)"
          style="flex: 4"
        />
        <div style="flex: 1"></div>
        <InputNumber
          prefix="Y: "
          :step="5"
        :max='timesheights'
        :maxlength="3"
          :value="top"
          @change="value => updateTop(value as number)"
          style="flex: 4"
        />
      </div>
      <template v-if="handleElement!.type !== 'line'">
        <div class="row">
          <InputNumber
            prefix="w: "
            :min="0"
            :max="3000"
            :step="5"
            :maxlength="4"
            :disabled="isVerticalText"
            :value="width"
            @change="value => updateWidth(value as number)"
            style="flex: 4"
          />
          <template
            v-if="['image', 'shape', 'audio'].includes(handleElement!.type)"
          >
            <Tooltip
              :mouseLeaveDelay="0"
              :mouseEnterDelay="0.5"
              title="解除宽高比锁定"
              v-if="fixedRatio"
            >
              <IconLock
                style="flex: 1"
                class="icon-btn"
                @click="updateFixedRatio(false)"
              />
            </Tooltip>
            <Tooltip
              :mouseLeaveDelay="0"
              :mouseEnterDelay="0.5"
              title="宽高比锁定"
              v-else
            >
              <IconUnlock
                style="flex: 1"
                class="icon-btn"
                @click="updateFixedRatio(true)"
              />
            </Tooltip>
          </template>
          <div style="flex: 1" v-else></div>
          <InputNumber
            prefix="h:"
            :min="0"
            :max="3000"
            :step="5"
            :maxlength="4"
            :value="height"
            @change="value => updateHeight(value as number)"
            style="flex: 4"
          />
        </div>
      </template>
      <template
        v-if="!['line', 'video', 'audio'].includes(handleElement!.type)"
      >
        <div class="row">
          <InputNumber
            prefix="旋转："
            :min="-180"
            :max="180"
            :step="5"
            :value="rotate"
            @change="value => updateRotate(value as number)"
            style="flex: 4"
          />
          <div style="flex: 1"></div>
          <div class="text-btn" @click="updateRotate45('-')" style="flex: 2.3">
            <IconRotate /> -45°
          </div>
          <div class="text-btn" @click="updateRotate45('+')" style="flex: 1.5">
            <IconRotate :style="{ transform: 'rotateY(180deg)' }" /> +45°
          </div>
        </div>
      </template>
    
      <Divider />
      <div class="info">视频设置</div>
    </div>
    <el-scrollbar height="600px">
      <div
        style="
          text-align: center;
          width: 100%;
          height: 100%;
          position: relative;
        "
        v-for="(video, index) in urls"
      >
        <video
          style="width: 100%"
          :key="index"
          :src="video"
          @ended="playNextVideo(index)"
        ></video>
        <!-- <div>
          <img
            src="../../../../assets/ti.png"
            alt=""
            style="
              width: 20px;
              height: 20px;
              position: absolute;
              top: 5px;
              right: 25px;
            "
          />
          <img
            src="../../../../assets/delect.png"
            alt=""
            @click="delect(index)"
            style="
              width: 20px;
              height: 20px;
              position: absolute;
              top: 5px;
              right: 0;
            "
          />
        </div> -->
      </div>
    </el-scrollbar>
    <Popover trigger="click" v-model:visible="showoss">
      <template #content>
        <videoOss
          @close="showoss = false"
          @insert-video="toinsertAudio"
        ></videoOss>
      </template>
      <Tooltip :mouseLeaveDelay="0" :mouseEnterDelay="0.5" title="添加视频">
        <el-button
          type="primary"
          class="full-width-btn"
          style="background-color: #0daeff"
        >
          <Iconopen class="btn-icon" />添加</el-button
        >
      </Tooltip>
    </Popover>
  </div>
</template>
<script lang="ts" setup>
import { ref, computed, watch, onBeforeMount, reactive } from "vue";
import { storeToRefs } from "pinia";
import videoOss from "../../CanvasTool/videoOss.vue";
import { useMainStore, useSlidesStore } from "@/store";
import { MIN_SIZE } from "@/configs/element";
import { SHAPE_PATH_FORMULAS } from "@/configs/shapes";
import { round } from "lodash";
import useHistorySnapshot from "@/hooks/useHistorySnapshot";
import {
  Divider,
  Button,
  InputNumber,
  Tooltip,
  Select,
  Input,
  message,
  Popover,
} from "ant-design-vue";
import {
  ENTER_ANIMATIONS,
  EXIT_ANIMATIONS,
  ATTENTION_ANIMATIONS,
} from "@/configs/animation";
const left = ref(0);
const top = ref(0);
const width = ref(0);
const height = ref(0);
const rotate = ref(0);
const fixedRatio = ref(false);
// 注意，存在一个未知原因的BUG，如果文本加粗后文本框高度增加，画布的可视区域定位会出现错误
// 因此在执行预置样式命令时，将加粗命令放在尽可能靠前的位置，避免字号增大后再加粗
// 删除
const delect = (e: any) => {
  urls.value.splice(e, 1);
};
import useViewportSize from '../../Editor/Canvas/hooks/useViewportSize'
const mainStore = useMainStore();
const {
  handleElement,
  handleElementId,
  richTextAttrs,
  availableFonts,
  canvasScale,
  textFormatPainter,
} = storeToRefs(mainStore);
const canvasRef = ref<HTMLElement>()
const { dragViewport, viewportStyles } = useViewportSize(canvasRef)
const fill = ref<string>("#000");
const lineHeight = ref<number>();
const wordSpace = ref<number>();
const textIndent = ref<number>();
const paragraphSpace = ref<number>();
watch(
  handleElement,
  () => {
    if (!handleElement.value || handleElement.value.type !== "image") return;

    fill.value = handleElement.value.fill || "#FFFFFFFF";
    lineHeight.value = handleElement.value.lineHeight || 1.5;
    wordSpace.value = handleElement.value.wordSpace || 0;
    textIndent.value = handleElement.value.textIndent || 0;
    paragraphSpace.value =
      handleElement.value.paragraphSpace === undefined
        ? 5
        : handleElement.value.paragraphSpace;
  },
  { deep: true, immediate: true }
);
const minSize = computed(() => {
  if (!handleElement.value) return 20;
  return MIN_SIZE[handleElement.value.type] || 20;
});
const animationEffects: { [key: string]: string } = {};
for (const effect of ENTER_ANIMATIONS) {
  for (const animation of effect.children) {
    animationEffects[animation.value] = animation.name;
  }
}
for (const effect of EXIT_ANIMATIONS) {
  for (const animation of effect.children) {
    animationEffects[animation.value] = animation.name;
  }
}
for (const effect of ATTENTION_ANIMATIONS) {
  for (const animation of effect.children) {
    animationEffects[animation.value] = animation.name;
  }
}

const slidesStore = useSlidesStore();
const { currentSlide } = storeToRefs(slidesStore);

watch(
  () => handleElementId.value,
  () => {
    animationPoolVisible.value = false;
  }
);

const animationPoolVisible = ref(false);

const isVerticalText = computed(() => {
  return handleElement.value?.type === "video" && handleElement.value.vertical;
});
watch(
  handleElement,
  () => {
    if (!handleElement.value) return;

    left.value = round(handleElement.value.left, 1);
    top.value = round(handleElement.value.top, 1);

    fixedRatio.value =
      "fixedRatio" in handleElement.value && !!handleElement.value.fixedRatio;

    if (handleElement.value.type !== "line") {
      width.value = round(handleElement.value.width, 1);
      height.value = round(handleElement.value.height, 1);
      rotate.value =
        "rotate" in handleElement.value &&
        handleElement.value.rotate !== undefined
          ? round(handleElement.value.rotate, 1)
          : 0;
    }
  },
  { deep: true, immediate: true }
);
const { addHistorySnapshot } = useHistorySnapshot();
var time = ref<any>((viewportStyles.value.width + 13) * canvasScale.value + 'px' )
var heights = ref<any>((viewportStyles.value.height + 13) * canvasScale.value + 'px' )
// 设置元素位置
var times = ref(Number(time.value.split(".")[0]))
var timesheights = ref(Number(heights.value.split(".")[0]))
// 设置元素位置
const updateLeft = (value: number) => {
  const props = { left: value };
  slidesStore.updateElement({ id: handleElementId.value, props });
  addHistorySnapshot();
};
const updateTop = (value: number) => {
  const props = { top: value };
  slidesStore.updateElement({ id: handleElementId.value, props });
  addHistorySnapshot();
};

// 设置元素宽度、高度、旋转角度
// 对形状设置宽高时，需要检查是否需要更新形状路径
const updateShapePathData = (width: number, height: number) => {
  if (
    handleElement.value &&
    handleElement.value.type === "shape" &&
    "pathFormula" in handleElement.value &&
    handleElement.value.pathFormula
  ) {
    const pathFormula = SHAPE_PATH_FORMULAS[handleElement.value.pathFormula];

    let path = "";
    if ("editable" in pathFormula)
      path = pathFormula.formula(width, height, handleElement.value.keypoint!);
    else path = pathFormula.formula(width, height);

    return {
      viewBox: [width, height],
      path,
    };
  }
  return null;
};
const updateWidth = (value: number) => {
  let props = { width: value };
  const shapePathData = updateShapePathData(value, height.value);
  if (shapePathData) props = { ...props, ...shapePathData };

  slidesStore.updateElement({ id: handleElementId.value, props });
  addHistorySnapshot();
};
const updateHeight = (value: number) => {
  let props = { height: value };
  const shapePathData = updateShapePathData(width.value, value);
  if (shapePathData) props = { ...props, ...shapePathData };

  slidesStore.updateElement({ id: handleElementId.value, props });
  addHistorySnapshot();
};
const updateRotate = (value: number) => {
  const props = { rotate: value };
  slidesStore.updateElement({ id: handleElementId.value, props });
  addHistorySnapshot();
};

// 固定元素的宽高比
const updateFixedRatio = (value: boolean) => {
  const props = { fixedRatio: value };
  slidesStore.updateElement({ id: handleElementId.value, props });
  addHistorySnapshot();
};

// 将元素旋转45度（顺时针或逆时针）
const updateRotate45 = (command: "+" | "-") => {
  let _rotate = Math.floor(rotate.value / 45) * 45;
  if (command === "+") _rotate = _rotate + 45;
  else if (command === "-") _rotate = _rotate - 45;

  if (_rotate < -180) _rotate = -180;
  if (_rotate > 180) _rotate = 180;

  const props = { rotate: _rotate };
  slidesStore.updateElement({ id: handleElementId.value, props });
  addHistorySnapshot();
};

// 设置富文本超链接
const linkPopoverVisible = ref(false);

watch(richTextAttrs, () => (linkPopoverVisible.value = false));

var showoss = ref(false);

const { slides } = storeToRefs(useSlidesStore());
var slide = ref(slides);
const state = reactive({
  videoInfo: slide.value[0].videoInfo,
});
const video = computed(() => state.videoInfo);

// 自动播放下一个
const liststatus = ref(0);
const playNextVideo = (e) => {
  if (liststatus.value < urls.value.length) {
    liststatus.value++;
  }
};
const toinsertAudio = (val: any) => {
  urls.value.push(val);
  showoss.value = false;
  slidesStore.updateElement({
    id: handleElementId.value,
    props: { urls: urls.value },
  });
};
const urls = ref([]);
var obj = slidesStore.currentSlide.elements.find(
  (v) => v.id == handleElementId.value
);
urls.value = obj.urls;
var srcs = ref([]);

onBeforeMount(() => {
  currentSlide.value.elements.forEach((item) => {
    srcs.value = item.urls;
  });
});
</script>

<style lang="scss" scoped>
$inColor: #68a490;
$outColor: #d86344;
$attentionColor: #e8b76a;

.element-animation-panel {
  height: 100%;
  display: flex;
  flex-direction: column;
}
.tabs {
  display: flex;
  justify-content: flex-start;
  align-items: center;
  border-bottom: 1px solid $borderColor;
  margin-bottom: 20px;
}
.tab {
  width: 33.33%;
  padding-bottom: 8px;
  border-bottom: 2px solid transparent;
  text-align: center;
  cursor: pointer;

  &.active {
    border-bottom: 2px solid $themeColor;
  }
  &.in.active {
    border-bottom-color: $inColor;
  }
  &.out.active {
    border-bottom-color: $outColor;
  }
  &.attention.active {
    border-bottom-color: $attentionColor;
  }
}
.element-animation {
  height: 32px;
  display: flex;
  align-items: center;
}
.element-animation-btn {
  width: 100%;
}
.config-item {
  display: flex;
  align-items: center;

  & + .config-item {
    margin-top: 5px;
  }
}
.tip {
  height: 32px;
  display: flex;
  justify-content: center;
  align-items: center;
  font-style: italic;
}
.animation-pool {
  width: 400px;
  height: 500px;
  overflow-y: auto;
  overflow-x: hidden;
  font-size: 12px;
  margin-right: -12px;
  position: relative;

  .mask {
    @include absolute-0();
  }

  &.in .type-title {
    border-left-color: $inColor;
    background-color: rgba($color: $inColor, $alpha: 0.15);
  }
  &.out .type-title {
    border-left-color: $outColor;
    background-color: rgba($color: $outColor, $alpha: 0.15);
  }
  &.attention .type-title {
    border-left-color: $attentionColor;
    background-color: rgba($color: $attentionColor, $alpha: 0.15);
  }
}
.type-title {
  width: 100%;
  font-size: 13px;
  margin-bottom: 10px;
  border-left: 4px solid #aaa;
  background-color: #eee;
  padding: 2px 0 2px 10px;
}
.pool-item-wrapper {
  @include flex-grid-layout();
}
.pool-item {
  @include flex-grid-layout-children(4, 24%);

  margin-bottom: 10px;
  height: 40px;
  line-height: 40px;
  text-align: center;
  cursor: pointer;
}
.animation-box {
  background-color: $lightGray;
}

.animation-sequence {
  flex: 1;
  padding-right: 12px;
  margin-right: -12px;

  @include overflow-overlay();
}
.sequence-item {
  border: 1px solid $borderColor;
  padding: 10px 6px;
  border-radius: $borderRadius;
  margin-bottom: 8px;
  transition: all 0.5s;

  &.in.active {
    border-color: $inColor;
  }
  &.out.active {
    border-color: $outColor;
  }
  &.attention.active {
    border-color: $attentionColor;
  }
  &.active {
    height: auto;
  }

  .sequence-content {
    display: flex;
    align-items: center;
    cursor: grab;

    &:active {
      cursor: grabbing;
    }

    .index {
      flex: 1;
    }
    .text {
      flex: 6;
    }
    .handler {
      flex: 2;
      font-size: 15px;
      text-align: right;
    }
    .handler-btn {
      margin-left: 8px;
      cursor: pointer;
    }
  }
}
.info {
  font-family: "PingFang SC";
  font-style: normal;
  font-weight: 500;
  font-size: 14px;
  line-height: 22px;
  /* identical to box height, or 157% */

  /* 文字色-次要文字or图标 */

  color: #8a8e92;
}
.text-style-panel {
  user-select: none;
}
.row {
  width: 100%;
  display: flex;
  align-items: center;
  margin-bottom: 10px;
}
.trgger {
  display: flex;
  align-items: center;
  justify-content: space-between;
  width: 100%;
}
.preset-style {
  display: flex;
  flex-wrap: wrap;
  margin-bottom: 10px;
}
.preset-style-item {
  width: 50%;
  height: 50px;
  border: solid 1px #d6d6d6;
  box-sizing: border-box;
  display: flex;
  justify-content: center;
  align-items: center;
  position: relative;
  cursor: pointer;
  transition: all $transitionDelay;

  &:hover {
    border-color: $themeColor;
    color: $themeColor;
    z-index: 1;
  }

  &:nth-child(2n) {
    margin-left: -1px;
  }
  &:nth-child(n + 3) {
    margin-top: -1px;
  }
}
.font-select {
  max-width: 50%;
}
.font-size-btn {
  padding: 0;
}
.link-popover {
  width: 240px;

  .btns {
    margin-top: 10px;
    text-align: right;
  }
}

.list-wrap {
  width: 176px;
  color: #666;
  padding: 8px;
  margin: -12px;
  display: flex;
  flex-wrap: wrap;
  align-content: flex-start;
}
.list {
  background-color: $lightGray;
  padding: 4px 4px 4px 20px;
  cursor: pointer;

  &:not(:nth-child(3n)) {
    margin-right: 8px;
  }

  &:nth-child(4),
  &:nth-child(5),
  &:nth-child(6) {
    margin-top: 8px;
  }

  &:hover {
    color: $themeColor;

    span {
      background-color: $themeColor;
    }
  }
}
.list-item {
  width: 24px;
  height: 12px;
  position: relative;
  top: -5px;

  span {
    width: 100%;
    height: 2px;
    display: inline-block;
    position: absolute;
    top: 10px;
    background-color: #666;
  }
}
.popover-btn {
  padding: 0 3px;
}
.row {
  width: 100%;
  display: flex;
  align-items: center;
  margin-bottom: 10px;
}
.switch-wrapper {
  text-align: right;
}
.origin-image {
  height: 100px;
  background-size: contain;
  background-repeat: no-repeat;
  background-position: center;
  background-color: $lightGray;
  margin-bottom: 10px;
}
.full-width-btn {
  width: 100%;
  margin-bottom: 10px;
}
.btn-icon {
  margin-right: 3px;
}

.clip {
  width: 260px;
  font-size: 12px;

  .title {
    margin-bottom: 5px;
  }
}
.shape-clip {
  margin-bottom: 10px;

  @include flex-grid-layout();
}
.shape-clip-item {
  display: flex;
  justify-content: center;
  align-items: center;
  cursor: pointer;

  @include flex-grid-layout-children(5, 16%);

  &:hover .shape {
    background-color: #ccc;
  }

  .shape {
    width: 40px;
    height: 40px;
    background-color: #e1e1e1;
  }
}
</style>
